//
//  MCDevice.h
//  ApexIOTCardSDK
//
//  Created by 黄亮东 on 16/5/10.
//  Copyright © 2016年 珠海艾派克科技股份有限公司. All rights reserved.
//
/**
 * 本SDK框架的入口；代表能够感应并且读取NFC卡片数据、并最终以一个卡片对象（标识码对象）、以及基本的信息和卡文件列表的系列软件，硬件、读卡器设备等功能组合。
 * 它包含手机中的软硬件模块直连NFC，也可以是BLE，WI-FI等与NFC适配；它包括厂家定义的一系列通讯命令，NFC卡操作命令，存储、压缩、解包、组包、加密解密等规范。
 *
 * Device是上层应用调用底层SDK功能实现的集中入口，不同的设备它的连接特性可能有所不同，但是其最终的目的都是为了实现基于卡片连接，以及文件数据存储访问的功能框架。
 *
 * @since 1.0
 * @version 1.0
 * @author ys
 *
 */
#import <Foundation/Foundation.h>
@class MCDeviceConnectEvent, MCDeviceConnectEvent, MCCardEvent, MCCardFileReader, MCCardFileWriter, MCCard;

typedef NS_ENUM(NSInteger, MCDeviceType){
    MCDeviceType_TYPE_NFC = 1,
    MCDeviceType_TYPE_BLE = 2,
    MCDeviceType_TYPE_WiFi = 3,
    MCDeviceType_None = 0
};
typedef NS_ENUM(NSInteger, MCDeviceMode){
    /*
     * 表示第三方开发上层应用的场景为只需要读取卡片的信息。
     */
    MCDeviceMode_READ_ONLY = 21,
    /*
     * 表示第三方开发上层应用的场景为只需要写卡片，此时用户随时会将空白或准备覆盖的卡片贴近。底层不应该自动将卡数据读到手机缓存中。
     */
    MCDeviceMode_WRITE_ONLY = 22,
    /**
     * 空闲状态表示本设备将暂停运作，不会处理数据读写作业。
     */
    MCDeviceMode_IDLE = 0
};

@protocol DeviceConnectListener <NSObject>
/**
 * 读卡器适配器与设备手机产生连接的时候，将触发事件并且调用本方法。
 *
 */
- (void)onDeviceConnected:(MCDeviceConnectEvent *)event;
/**
 * 读卡器适配器与设备手机断开时将触发该事件并调用此方法。
 *
 */
- (void)onDeviceDisconnect:(MCDeviceConnectEvent *)event;

@end

@protocol CardListener <NSObject>
@required
/**
 * 卡片贴紧到NFC手机设备上或读卡器上，并且被感应到成功识别和驱动连接中。
 *
 * 此方法在卡片每次重新被感应到，都会调用。
 *
 * @param event
 */
- (void)onCardAttached:(MCCardEvent *)event;
/**
 * 卡片失去连接，或者卡片连接发生错误。
 *
 * 此方法在卡片每次连接超时或者感应范围失效导致需要重新连接的时候，都会调用。
 *
 * @param event
 */
- (void)onCardUnattached:(MCCardEvent *)event;
/**
 *
 * 设备读取的卡片（比对贴近的卡片头与已经锁定的卡片头信息如果不一样）有变更的时候，将会触发该监听器的方法。
 *
 * @param event
 */
- (void)onCardChanged:(MCCardEvent *)event;
/**
 *
 * 当前卡片已经有进入事务会话的时候，另外一张卡片进来将会触发想要变更卡片的事件。
 * 系统应该根据用户的需求，决定是否弹出提示，由用户决定是否需要强制将当前的卡片退出事务。
 *
 * @param event
 */
- (void)onCardNotApplicable:(MCCardEvent *)event;
/**
 * 卡片产生一次读取进度将被调用。
 *
 * @param event
 */
- (void)onCardTotalProgress:(MCCardEvent *)event;
/**
 * 卡片全部读取完毕将被调用
 *
 * @param event
 */
- (void)onCardTotalFinished:(MCCardEvent *)event;

@end

@interface MCDevice : NSObject
/**
 * 读卡设备状态监听器。
 *
 * @param listener
 */
@property (nonatomic, weak) id<DeviceConnectListener>deviceConnectListener;
/**
 * 卡片监听器。
 *
 * 监听读卡设备范围内，卡片的变化情况。
 * 包括：
 * 1、一张新卡被读取时候，触发onCardChanged事件
 * 2、当前有卡锁定的情况下，另外一张卡片被读取时，触发onCardNotApplicable事件
 *
 * @param listener
 */
@property (nonatomic, weak) id<CardListener>cardListener;

/**
 * 设备类型。
 */
@property (nonatomic, assign) MCDeviceType type;

/**
 * 检查当前设备是否为连接状态。
 */
@property (nonatomic, assign, readonly) BOOL isEnable;

/**
 * 如果为只读模式，底层将会可能提供缓冲区功能，只要卡片一接近，将会可能提前将数据读到底层缓冲区中。
 *
 * 本方法应该在底层还没有开始对某张卡片读写的时候进行调用，当本方法已经进入读写状态的时候，否则不应该直接调用，
 * 相应的模式应该是在成功调用getCardFileRreader或者getCardFileWriter方法之后，来决定决定当前Device的状态。
 *
 * 需要配合CardFileReader或者CardFileWriter实例中的close方法进行结合使用。
 *
 */
@property (nonatomic, assign) MCDeviceMode mode;
/**
 * 获得卡文件读取对象
 */
@property (nonatomic, strong, readonly) MCCardFileReader *cardFileReader;
/**
 * 获得卡文件写入对象
 */
@property (nonatomic, strong, readonly) MCCardFileWriter *cardFileWriter;
/**
 * 返回当前锁定的卡片。
 */
@property (nonatomic, strong, readonly) MCCard *lockedCard;
/**
 * 当前是否有卡片贴近
 */
@property (nonatomic, assign, readonly) BOOL isCardAttached;
/**
 * 返回当前贴近的卡片。
 */
@property (nonatomic, assign, readonly) MCCard *attachedCard;

/**
 * 锁定当前卡片或指定的卡片，调用该方法的时候，如果当前有锁定的卡片，将会抛出异常。
 *
 * 该方法不建议直接调用，通常是通过MCCardFileReader的read方法或者MCCardFileWriter的write方法来锁定卡片。
 *
 * @param card
 *
 * @return 当前已有锁定的卡片，将返回NO，请先将其解锁
 */
- (BOOL)lock:(MCCard *)card;
/**
 * 释放当前被锁定的卡片，如果当前没有锁定的卡片，则无需做任何操作。
 *
 *
 */
- (void)unlock;

@end
